import java.util.ArrayList;
import java.util.Collections;
import java.util.LinkedList;
import java.util.List;

/**
 * @author ZhiWen Ren
 * @version 1.0
 * @description: LeetCode-394-字符串解码
 * @date 2025/6/10 10:44
 */
public class Soloution394 {
    public static void main(String[] args) {
        System.out.println(decodeString("3[a]2[bc]"));
    }
    private static int ptr;

    public static String decodeString(String s) {
        LinkedList<String> stack = new LinkedList<>();
        ptr = 0;
        while (ptr < s.length()) {
            Character c = s.charAt(ptr);
            if (Character.isDigit(c)) {
                // 若是数字，则一连串的处理数字，并进栈stack,函数内部已实现ptr++
                String digits = getDigit(s);
                stack.addLast(digits);
            } else if (Character.isLetter(c) || '[' == c) {
                // 若是字母或者’[‘，则直接进栈
                stack.addLast(String.valueOf(c));
                ptr++;
            } else {
                // 右括号,出栈后再进栈
                List<String> subStrList = new ArrayList<>();
                while (!stack.get(stack.size() - 1).equals("[")) {
                    // 一直出栈到“[”为止
                    subStrList.add(stack.removeLast());
                }
                Collections.reverse(subStrList);
                String subStr = getString(subStrList);
                // 左括号出栈
                stack.removeLast();
                // 这时栈顶元素是需要重复的数字次数
                int repeatNum = Integer.parseInt(stack.removeLast());
                StringBuilder temp = new StringBuilder();
                while (repeatNum > 0) {
                    temp.append(subStr);
                    repeatNum--;
                }
                stack.addLast(temp.toString());
                ptr++;
            }
        }
        return getString(stack);
    }

    public static String getDigit(String s) {
        StringBuffer stringBuffer = new StringBuffer();
        while (Character.isDigit(s.charAt(ptr))) {
            // 如果ptr后面的还是数字，就继续处理为字符串
            stringBuffer.append(s.charAt(ptr++));
        }
        return stringBuffer.toString();
    }

    public static String getString(List<String> s) {
        StringBuffer stringBuffer = new StringBuffer();
        for (String x : s) {
            stringBuffer.append(x);
        }
        return stringBuffer.toString();
    }
}
